\chapter{Das Projekt}
\label{chap:proj}
In diesem Kapitel setze ich mich mit dem Entwicklungprozess des geforderten Moduls auseinander. Als erstes erl\"autere ich die theoretische Planung und Entwicklung des Moduls, um ein gemeinsames Verst\"andnis herzustellen. Die einzelnen Schritte und Komponente werden in den Unterkapiteln bearbeitet sowie durch praxisbezogene Codebeispiele beschrieben und mit Hilfe der aufgezeichneten Diagramme verdeutlicht. Das von mir zu entwickelnde Modul bildet dabei einen Baustein eines gr\"o\ss{}eren Projekts [\ref{sec:zielderarbeit}] der Firma pAppermint.\\
Von der Firma wird ein eigener, sich aktuell in Weiterentwicklung befindender Installationswizard zur Verf\"ugung gestellt, der bei der erstmaligen Einrichtung sowie zum sp\"ateren Update nach der Erg\"anzung des Systems um weitere Module behilflich ist. Zus\"atzlich werden die \textit{Zend Action Controller} und \textit{Zend\_Db\_Table\_Abstract} erweitert, sodass beim Hinzuf\"ugen eines neuen Moduls die grundlegenden Datenbankfunktionalit\"aten "`Anzeigen"', "'Hinzuf\"ugen"', "'\"Andern"' und "'L\"oschen"' m\"oglich sind.


%
%---------------------------------------------------------------------
%
\section{Analyse und Design}
\label{proj:analysdesign}
Die Analyse der erhobenen Spezifikationen im Kapitel \ref{chap:anforderungen} ergibt bestimmte Anwendungsf\"alle des zu erstellenden Moduls. Einen dynamischen Aspekt dieser F\"alle verschaffen Sequenzdiagramme, die das Verhalten und die Wechselbeziehungen der einzelnen Auspr\"agungsmittel darstellen.\\
Wie bereits in der Einleitung im Kapitel \ref{sec:zielderarbeit} beschrieben ist das zu entwickelnde Modul in eine vorhandene Plattform zu integrieren, welche mit einem Userverwaltungsmechanismus versehen ist. Die Schnittstellen und die dazugeh\"origen Datenquellen sind von einem Benutzer oder einer Benutzergruppe zu verwalten.\\
Die Schnittstellen werden im Rahmen dieser Bachelorthese auch als Sichten (englisch "`views"') bezeichnet, da sie als k\"unftig vom Client angeforderte Daten eine Art einheitlich definierte Sicht auf die Ursprungsdatenmengen bieten.\\
F\"ur die Erstellung der Diagrammgraphiken wird das Programm \textit{Visual Paradigm for UML}\footnote{Visual Paradigm for UML Community Edition in der Version 10.2 (Build 20130710) \url{http://www.visual-paradigm.com/}.} verwendet, das f\"ur nicht-kommerzielle Nutzung kostenfrei zur Verf\"ugung steht.
\\
Meine Konzeption zur Realisierung des Projektes sieht dabei Folgendes vor. 

Das System besteht aus einer graphischen Weboberfl\"ache [Kapitel \ref{proj:ui}], die f\"ur die Interaktion mit dem Administrator und die Entgegennahme der Konfigurationen zust\"andig ist. Die Konfigurationen der ausw\"artigen Quellen, der Struktur und des Formats der auszugebenden Daten werden in einer lokalen Datenbank gespeichert und sind somit jederzeit f\"ur das System greifbar.\\
Die eigentliche Funktionalit\"at lagere ich in eine \textit{Software Develoment Kit (SDK)} [Kapitel \ref{proj:sdk}] aus.

\begin{figure}[htbp]
		\centering
		\includegraphics[width=10cm]{media/grobeArchitektur.PNG}
		\caption{Grobe Architektur}
		\label{fig:grobeacrchitektur}
	\end{figure}
	
	In der Abbildung \ref{fig:grundconfig} ist das Zusammenspiel der Benutzer mit der Systemfront zur Konfiguration der Schnittstelle und zur Eingabe der ben\"otigten Informationen zwecks sp\"aterer Anbindung der Datenquellen dargestellt. Dazu ruft der Administartor die Webseite auf. Diese stellt die zu diesem Zeitpunkt vorhandenen Datenquellen als eine Liste dar. Der Administrator kann diese \"andern, entfernen oder neue Datenquellen hinzuf\"ugen. Zu den Eingaben an dieser Stelle geh\"oren alle zum Zwecke des Ansprechens einer Quelle erforderlichen Informationen wie Host, IP-Adressen und Login-Daten. Die externen Datenquellen werden mit Hilfe von Adaptern [Kapitel \ref{proj:adapter}] an das System angebunden.\\
	Im n\"achsten Schritt werden die Schnittstellen definiert. Eine Auflistung der aktuell vorhandenen Schnittstellen verschafft eine \"Ubersicht. Hier k\"onnen die Sichten editiert oder hinzugef\"ugt werden. Die Quellen geh\"oren ebenso zu den Konfigurationen einer Schnittstelle und werden in einer lokalen Datenbank gespeichert.

\begin{figure}[htbp]
		\centering
		\includegraphics[width=12cm]{media/grundconfig.PNG}
		\caption{Sequenzdiagramm: Quellen und Schnittstellenkonfiguration}
		\label{fig:grundconfig}
	\end{figure}
	
	\newpage
	
	Darauffolgend soll die Struktur der Ausgangsdaten festgelegt werden. Dazu reduziere ich die Datenmenge zum besseren Verst\"andnis mit Hilfe der Abstraktion auf Tabellen mit Attributen als Spalten. Der Administrator w\"ahlt die Datenmengen von den zur Verf\"ugung stehenden Datenquellen aus und selektiert anschlie\ss{}end die jeweiligen Attribute. Stammen die Daten oder Teile davon aus einer Datei, wird diese erst geparst und die Informationen werden an das Frontend delegiert. Au\ss{}erdem erfolgen die Angaben zum Zusammenf\"uhren der Tabellen zu einer Tabelle, indem die zuvor ausgew\"ahlten Attribute als zusammengeh\"orend bezeichnet werden. Damit entstehen die Regeln zum Mergen der Tabellen. Die gesamten durchgef\"uhrten Arbeitsschritte werden dabei ebenfalls in der lokalen Datenbank gespeichert. Eine Illustrierung bietet die folgende Grafik \ref{fig:sichtdefdatastruk}.
	
\begin{figure}[htbp]
		\centering
		\includegraphics[width=14cm]{media/sichtdefdatastruk.PNG}
		\caption{Sichtdefinition: Festlegung der Struktur der Ausgangsdaten}
		\label{fig:sichtdefdatastruk}
	\end{figure}
	
	\newpage
	
	Alles in allem geh\"oren zum Konfigurationsprozess Einstellungen zum Erfassen der externen Quellen, zu den Sichten sowie zur Struktur der Daten, Formate und Cachedauer.
	
	\begin{figure}[htbp]
		\centering
		\includegraphics[width=12cm]{media/sichtconf.PNG}
		\caption{Konfigurierbare Elemente}
		\label{fig:sichtconf}
	\end{figure}

Nach der Einstellung der Parameter k\"onnen die Clients mit Daten versorgt werden. Die asynchronen Anfragen erfolgen an die Schnittstellen mit der \"Ubergabe bestimmter Parameter, zum Beispiel des Sichtnamens. Die Software untersucht den Cache auf bestehende und noch g\"ultige Eintr\"age zur eingegangenen Anfrage. Bei Vorhandensein eines Eintrags wird dieser gelesen und an den anfragenden Client weitergegeben. Anderenfalls sammelt die Software die Konfigurationsaufzeichnungen aus der lokalen Datenbank. Mit Hilfe dieser werden die gew\"unschten Datenmengen aus den externen Datenquellen aufgerufen und anhand der Regelungen aus der lokalen Datenbank gemergt. Anschlie\ss{}end werden die Ergebnisse an die Cachekomponente zur Zwischenspeicherung weitergegeben und der Prozess endet mit der Ausgabe an den Client.

\begin{figure}[htbp]
		\centering
		\includegraphics[width=14cm]{media/clientabfragesicht.jpg}
		\caption{Prozess bei Clientabfragen}
		\label{fig:prozessclientabfragen}
	\end{figure}
	
	\newpage
	
	\subsection{Datenbankschema}
	\label{proj:dbschema}
	Wie im Kapitel \ref{proj:analysdesign} beschrieben, speichere ich die Konfigurationen in einer lokalen Datenbank. Das Entity Relationship Diagramm \ref{fig:dber} zeigt mein Design f\"ur die Datenbank. Die Tabelle \textit{Project/User} soll hierbei die Ausarbeitung der Usermanagementfunktionalit\"at des Systems der Firma pAppermint [Kapitel \ref{chap:einleitung}] beschreiben. Sie besagt, dass eine Schnittstelle und deren Konfiguration zu einem Projekt, einem User oder einer Usergruppe geh\"oren und von diesen zu verwalten sind.\\
	Zu einer Schnittstelle geh\"oren mehrere Adapter. Diese repr\"asentieren die externen Datenquellen aus der Sicht der Datenbank und sind durch einen Prim\"arschl\"ussel eindeutig identifizierbar. Die Adapter sind typisiert. Ein Fremdschl\"ussel referenziert auf einen Eintrag in der Tabelle \textit{Driver}, in der diese Adaptertypen gespeichert werden. Mehrere Sichten k\"onnen auf die zu einer Konfiguration geh\"orenden Adapter zugreifen. Eine Sicht verf\"ugt \"uber die Attribute als Referenz auf das Ausgabeformat wie "`JSON"' oder "`XML"', das in der Tabelle \textit{Format} vorhanden ist. Diese Sicht verf\"ugt \"uber eine Identifikationsnummer, im Rahmen dieses Projekts soll der Name jedoch eindeutig dargestellt werden.\\
	Die Entity \textit{Tables} weist die Datenmengen auf. Es herrscht ein One-to-Many-Verh\"altnis zwischen \textit{View} und \textit{Tables}. Durch die Beziehung der Fremdschl\"ussel eines Adapters erkennt man den Ursprung der Daten. Der Administrator kann bestimmte Attribute aus der Tupel einer Tabelle ausw\"ahlen. Diese Auswahl wird in der Tabelle \textit{Columns} gespeichert. Eine \textit{View} ben\"otigt ebenso die Informationen zur Zusammenf\"uhrung der Daten. Dazu existiert die Entity \textit{Join}. Da die Reihenfolge, in welcher die Daten zusammengebracht werden, eine wichtige Rolle spielt, besitzt diese Tabelle zwei ID-Eintr\"age von Tables, die jeweils als "`links"' oder "`rechts"' bezeichnet werden. F\"ur die Information \"uber die Schl\"usselelemente zur Vereinigung der Daten sind die \textit{Join\_Columns} verantwortlich. Zu einer \textit{Join}-Operation geh\"oren mehrere Spalten, wie die dargestellte One-to-Many-Beziehung im Diagramm zeigt.
	
	\begin{figure}[htbp]
		\centering
		\includegraphics[width=14cm]{media/dber.PNG}
		\caption{Entity Relationship Diagramm}
		\label{fig:dber}
	\end{figure}
	
	\clearpage

%
%---------------------------------------------------------------------
%
\section{SDK}
\label{proj:sdk}
Mit dem \textit{Software Development Kit} soll eine Sammlung von Klassen und Skripten erstellt werden. Dieses wird als Bibliothek im Zend Framework eingebunden. Es dient zur Funktionalit\"atenkapselung und somit zur Gewinnung von Flexibilit\"at, zur \"Ubersicht sowie einer einfacheren Wartung und Pflege des Moduls.\\
Das SDK kann dementsprechend in anderen Modulen zum Einsatz kommen. Es enth\"alt beispielsweise die Adapterklassen [Kapitel \ref{proj:adapter}], den Cachemechanismus [Kapitel \ref{proj:caching}] und in Anlehnung an das Zend Framework die "`Action Helper"'-Klassen [Kapitel \ref{subsec:zend}].

	\begin{figure}[htbp]
		\centering
		\includegraphics[width=5cm]{media/sdklibrary.PNG}
		\caption{\texttt{library} mit der SDK-Ordnerstruktur}
		\label{fig:sdklib}
	\end{figure}	
	
	
	\subsection{Die Helferklasse DbProcedureCaller}
	\label{proj:sdkdbprocedcaller}
	Das Zend Framework bietet mit den \textit{Action Helpern} einen Weg, um Funktionalit\"aten auszulagern und folglich den Projektcode besser zu organisieren. Aus diesem Grund existiert die Klasse \textit{DbProcedureCaller}. Ihre Methoden vereinfachen das Aufrufen von Datenbankprozeduren, die beim Datenbankaufbau [Kapitel \ref{proj:dbaufbau}] entstanden sind. Die Methode \texttt{callProcedureByName(\$db, \$procedureName, \$procedureParams = null, ...)} bekommt als Parameter ein "`Zend\_Db\_Table"'-Objekt, den Namen der aufzurufenden Datenbankprozedur mit zugeh\"origen Parametern als ein einfaches Array. Sie setzt die Datenbankanfrage an und liefert die Ergebnisse zur\"uck. Die Methode \texttt{callProcedureLoopByName(...)} f\"uhrt die gleiche Prozedur f\"ur mehrere Parameter durch als ein verschachteltes Array. Weitere Funktionen, die "`AsTransaction"' im Namen enthalten, rufen die Stored-Procedure als eine geschlossene Transaktion auf. Dies geschieht beim Aufruf der von Zend bereitgestellten Methode \texttt{beginTransaction()}. Im \texttt{try-catch}-Block k\"onnen im Erfolgsfall die \"Anderungen mit \textit{commit()} festgeschrieben werden, anderenfalls wird \textit{rollBack()} gestartet.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected,try,catch,throw},
		firstline=97,lastline=151,
		captionpos=b,
		caption={Helferklasse DbProcedureCaller},
		label=code:phpdbproccaller]{media/phpcode.php}
	
	
	
%
%---------------------------------------------------------------------
%
\section{Datenbankaufbau}
\label{proj:dbaufbau}
Bei der Umsetzung meines theoretischen Entwurfs der Software kommt auf Grund der einfachen Installation und Einrichtung \textit{MySQL} als relationale Datenbank zum Zweck der lokalen Datenspeicherung zum Einsatz. Anhand des im Kapitel \ref{proj:dbschema} entworfenen Schemas erfolgt die Implemetierung der Tabellen und deren Beziehungen zueinander. F\"ur die referenzielle Integrit\"at und Transaktionssicherheit verwende ich die Speicher-Engine \textit{innoDB}, die dank der  COMMIT- und ROLLBACK-Mechanismen eine Datenwiederherstellungsf\"ahigkeit besitzt.\\
Die Adaptertabelle besteht aus den Spalten der Logindaten (\textit{user}, \textit{pw}) zu einer Datenbank oder FTP-Server sowie \textit{host}, \textit{port} und \textit{db} zur Verbindungsherstellung mit einer Datenbank. Die Elemente \textit{path}, \textit{filename} und \textit{delimiter} sind f\"ur Dateiquellen gedacht. Der Typ eines Adapters wird durch den Fremdschl\"ussel \textit{driver\_id} in der Tabelle \textit{Driver} eingegeben.
\\
\lstinputlisting[
		language=SQL,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		firstline=42,lastline=62,
		caption={Adaptertabelle},
		captionpos=b,
		label=code:adaptersql]{media/Synthese.sql}

Bei der Tabelle \textit{View} \ref{code:viewsql} wird deutlich, dass beide Felder \textit{name} und \textit{project\_id} mit der Eigenschaft "`UNIQUE"' versehen sind. Trotz des Attributes \textit{id} zur einfachen Identifikation sorgt "`UNIQUE"' in diesem Fall f\"ur eine eindeutige Kombination. Das bedeutet, dass im Rahmen des Projektes eine Sicht jeweils einmalig vorkommen darf.
\\
\lstinputlisting[
		language=SQL,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		firstline=20,lastline=26,
		caption={Viewtabelle},
		captionpos=b,
		label=code:viewsql]{media/Synthese.sql}

Nach der Erstellung der Tabellen erreiche ich unter Verwendung der \textit{Foreigen Key Constraints} die Wahrung der Konsistenz der Datenbest\"ande. Der folgende SQL-Code zeigt die Wechselbeziehungen und Einschr\"ankungen, die zwischen den einzelnen Tabellen zustandekommen.
\\
\lstinputlisting[
		language=SQL,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		firstline=95,lastline=113,
		caption={Fremdschl\"usselbeziehungen},
		captionpos=b,
		label=code:constraintssql]{media/Synthese.sql}

Aufgrund der etwas komplexeren Verflechtung der Abh\"angigkeiten und zur Wahrung der vollen Kontrolle \"uber de Datenbankoperationen verzichte ich auf die automatisierten "`CASCADE"'-Mechanismen. Au\ss{}erdem soll damit erreicht werden, dass m\"oglichst viele Datenbankoperationen auf die SQL-Ebene ausgelagert werden, da diese wesentlich schneller arbeitet als PHP.\\
Stattdessen implementiere ich hierf\"ur eigene gespeicherte Prozeduren. Die sogenannte \textit{Stored Procedure} erm\"oglicht mir die volle Kontrolle \"uber die Lese- und Schreiboperationen. Folgendes Beispiel soll demonstrieren, wie das Entfernen eines Eintrags aus der Tabelle \textit{Columns} funktioniert. Zuerst werden die betroffenen Zeilen aus den referenzierten Tabellen entfernt, anderenfalls verbietet das Datenbankmanagementsystem die L\"oschtransaktion. Wie in der Abbildung \ref{fig:dber} zu erkennen ist, werden die Zeilen aus den Tabellen \textit{Join\_Columns} entfernt. Sollten keine Eintr\"age mehr existieren, die zu einem \textit{Join} geh\"oren, kann dieser ebenfalls entfernt werden. Erst darauffolgend wird die die gew\"unschte Zeile entfernt werden. Dazu verwende ich "`CURSOR"' zum Abarbeiten mehrerer Zeilen als Ergebnis einer Abfrage. Dabei ist zu beachten, dass die Selbstdeklaration vor der Deklaration von Variablen und Handlern stattfinden muss. 
\\
\lstinputlisting[
		language=SQL,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		firstline=197,lastline=226,
		caption={gespeicherte Prozeduren},
		captionpos=b,
		label=code:storedprocsql]{media/Synthese.sql}

Das vollst\"andige Skript ist im Anhang [\ref{anhang:sqlkomplett}] dieser Ausarbeitung zu finden. Die \textit{START\_TRANSACTION}, \textit{COMMIT} oder \textit{ROLLBACK}-Anweisungen sind nicht im Skript zu finden, diese befinden sich angelehnt an das Zend Framework Tutorial im PHP-Code. Grund daf\"ur ist einerseits die Benennung der Anweisungen selbst und andererseits die Fehlerbehandlung je nach Datenbankmanagementsystem abweichend vom Standard. Damit soll der Portieraufwand des SQL-Skriptes minimiert werden.

%
%---------------------------------------------------------------------
%
\section{Implementierung der Weboberfl\"ache}
\label{proj:ui}
Die Konfiguration der Schnittstellen und der externen Datenquellen erfolgt \"uber eine Webseite. Bei der Entwicklung benutze ich JavaScript und die \textit{JavaScript}-Bibleothek \textit{jQuery} in der Version 2.0.3 f\"ur h\"ohere Benutzerfreundlichkeit. Zus\"atzlich verwende ich Elemente von \textit{jQueryUI} (Version 1.8.21) und den JQuery-Plugin \textit{DataTables} in der Version 1.9.4. \textit{DataTables} bietet HTML-Tabellen erweiterte Interaktionskontrolle wie Suchfunktion, Sortierfunktion und einen Paginator.\\
Zum Programmieren der Webseite erstelle ich ein Modul mit Hilfe der ZendFramework-Kommandozeilenkonsole [Kapitel \ref{subsubsec:shell}]. Das Modul nennt sich Synthese. Das geschieht mit der Eingabe des Befehls \texttt{zf create module Synthese}. 

Dies bewirkt, dass die Zend Shell den Modulordner Namens \texttt{Synthese} im \texttt{pplication/modules} erstellt und zus\"atzlich folgende Ordnerstruktur basierend auf dem MVC-Pattern [Kapitel \ref{subsec:mvc} und \ref{subsubsec:appzend}] vorbereitet.\\
\texttt{
	Synthese/controllers\\
	Synthese/model\\
	Synthese/view\\
	Synthese/view/scripts\\
	Synthese/view/helpers\\
	Synthese/view/filters\\
}\\

\subsection{Adapter- und Schnittstellenfinitionen}
F\"ur die externen Datenquellenbindungen benutze ich die von pAppermint erweiterten "`BaseController"' und "`BaseModel"', die bei der Einleitung im Kapitel \ref{chap:proj} angesprochen werden. Diese greifen auf die vorgefertigten und einheitlich designten Viewskripte zu, die XHTML und inline PHP Code enhalten.\\
Mit der Zend-Konsole erzeuge ich einen Controller und nenne ihn "`ConfigAdapter"' \texttt{zf create controller ConfigAdapter} \texttt{index-action-included=1 Synthese}. Damit erstellt die Konsole unter anderem die Datei \texttt{Synthese/controllers/ConfigAdapterController.php} mit zwei Methoden Namens \texttt{init} und \texttt{indexAction}.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=2,lastline=14,
		captionpos=b,
		caption={Controller zur Konfiguration der Datenquellen},
		label=code:phpconfigcontroller]{media/phpcode.php}

Durch den Einsatz des \texttt{Zend\_Loader} wird in der \texttt{init}-Methode der Namenspace meiner SDK registriert, damit sie vom Autoloader zur laufzeit geladen werden kann. Dazu werden in der Basisklasse konstitutive Punkte abgearbeitet. Es wird zum Beispiel die Verbindung zur Datenbank hergestellt. Die Authentifizierung und Authorisierung der Benutzer wird gepr\"uft. Die \texttt{Zend\_Session} kann hier ebenfalls gestartet werden. Manche Features werden vom ZendFramework \"ubernommen, k\"onnen jedoch beeinflusst werden. Das Model repr\"asentiert im Rahmen dieses Webprojektes eine Datenbanktabelle, aus diesem Grund ist das Model vom Typ \texttt{Zend\_Db\_Table\_Abstract}, in diesem Fall am besten geeignet. Ein Model l\"asst sich mit der Konsoleneingabe \texttt{zf create db-table name actual-table-name module} kreieren. Hier erstellt die Shell einen Unterordner Namens "`DbTable"' und ein Skript "`Adapter.php"' wie folgt \texttt{modules/Synthese/models/DbTable/Adapter.php}. Der folgende Code zeigt die weitere Implementierung des Models mit der BaseModel als Basisklasse. Danach kann die URL \texttt{http://host/synthese/configadapter/index} im Menu erlinkt werden, dabei ist die Eingabe der Action "`index"' optional, da Zend stets bei fehlender Actionbennenung die index-Action ansprechen wird.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=16,lastline=37,
		captionpos=b,
		caption={Einsatz des BaseModels},
		label=code:phpbasemodel]{media/phpcode.php}

Die Eigenschaften \texttt{\$\_name} und \texttt{\$\_primary} weisen auf den Tabellennamen und den Prim\"arschl\"ussel der Tabelle hin und sind Attribute der Vaterklasse "`Zend\_Db\_Table\_Abstract"'. Bei zusammengesetzten Schl\"usseln kann ein Array mit dem Spaltennamen als Wert eingegeben werden.\\
Die gleiche Prozedur wiederhole ich f\"ur die Datenbanktabellen "`Driver"', "`Format"'. Genauso wird mit der "`View"'-Tabelle verfahren. Es entsteht der Controller "`ConfigView"' und anschlie\ss{}end das Model "`View"'. Diese werden mit weiteren Methoden \texttt{findViewById(\$viewId)} und \texttt{findViewByProjectAndName(\$rojectId, \$name)} versehen, die anhand der \"ubergebenen Parameter die Sichtdaten aus der lokalen Datenbank zur\"uckliefern. Nach der \"Anderung der Subklassen zur "`BaseController"' und "`BaseModel"' steht eine Benutzeroberfl\"ache mit CRUD-Operationen zur Verwaltung der Adapter und Views bereit.\\
Die folgende Graphik zeigt die Ergebnisse im Browser. Als Beispiel zeige ich die Sichtkonfigurationsansicht.
\begin{figure}[htbp]
	\centering
	\includegraphics[width=13cm]{media/uiconfigview.PNG}
	\caption{Benutzeroberfl\"ache zur Verwaltung von Sichten}
	\label{fig:uiconfigview}
\end{figure}


\subsection{Konfigurationsassistent (Wizard)}

\subsubsection{Datenmengenauswahl}
\label{proj:tabellenauswahl}
Bei einem Klick auf eine Zeile in der \"Ubersichtstabelle in der Abbildung \ref{fig:uiconfigview} wird man von einem Assistenten zur Fertigstellung der Konfiguration begleitet. Diesbez\"uglich ben\"otige ich einen Actioncontroller mit dem Namen "`ConfigController"', in dem die jeweiligen Actions der Ablaufsfolge des Assistenten bewerkstelligt werden. Zuvor werden die Models f\"ur die jewiligen Tabellen in der lokalen Datenbank erstellt. Letztere erben von der Klasse "`Zend\_Db\_Table\_Abstract"' und werden mit den zwei Datenelementen \texttt{protected \$\_name} und \texttt{protected \$\_primary} best\"uckt.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=40,lastline=44,
		captionpos=b,
		caption={Join-Model},
		label=code:phpjoinmodel]{media/phpcode.php}

Der erste Schritt besteht in der Auswahl aus den nach ihrer Herkunft gruppierten Datenmengen aus einer Kollektion. Um dies zu erm\"oglichen, f\"uge ich die "`tableAction"' zum "`ConfigController"' hinzu. In dieser Funktion instanziiere ich zuerst das Model, in dem die getroffene Auswahl gespeichert wird. Danach werden die Instanzen der ben\"otigten Adapter erzeugt, um den Zugrif auf die externen Quellen zu bewerkstelligen.  Genaueres dazu wird im Kapitel \ref{proj:adapter} beschrieben. Im Anschluss werden diese Informationen mit \texttt{\$this->view->Daten} an das Viewobjekt weitergereicht.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=46,lastline=84,
		captionpos=b,
		caption={tableAction im ConfigController},
		label=code:phptableaction]{media/phpcode.php}

Um sie im Browser darzustellen, kann man auf die \"ubergebenen Daten im phtml-Skript\footnote{Phtml: Steht f\"ur PHP und HTML, ist eine Extension f\"ur die Viewskripte, in denen das HTML, CSS, JavaScript Code zu finden ist und f\"ur die verarbeitung von dynamischen Daten weiterhin inline PHP Code beeinhalten.} mit \texttt{\$this->Daten} zur\"uckgreifen. Die phtml-Skripte sind im Modul \texttt{Synthese/views/scripts/} in Unterordnern, die den Namen des Controllers tragen, organisiert. Die Skripte selbst tragen die Namen des Action. So k\"onnen sie von Zend erkannt und zugeordnet werden. Als ein Beispel in diesem Fall \texttt{Synthese/views/scripts/config/tables.phtml}, bei dem der Controller "`config"' hei\ss{}t und der Action "`tables"'.\\
Der Administrator trifft seine Wahl. Diese wird per Ajax an den Actioncontroller \"ubermittelt und in der lokalen Datenbank gespeichert. Zu diesem Zweck registriere ich einen \textit{submit}-Eventhandler f\"ur das Formular. In der EVenthandlerfunktion, serialisiere ich die Benutzereingaben und setze eine Ajax-Anfrage an, die Daten als POST-Parameter in einem Jsonformat an den Server \"ubermittelt und auf eine Antwort wartet.
\\
\lstinputlisting[
		language=Java,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,\$},
		firstline=1,lastline=25,
		captionpos=b,
		caption={Submit-Eventhandler mit Ajax},
		label=code:jssubmitajax]{media/javascript.js}
		
Nach der \"Uberpr\"ufung der Parameter der Ajaxanfage auf dem Server k\"onnen die in einer Zeichenkette serialisierten Daten mit \texttt{void parse\_str(\$str, \$arr)} wieder in ein Array umgewandelt und in der Variable \texttt{\$arr} zur Verf\"ugung gestellt werden [sieh Codeabbildung \ref{code:phptableaction}]. Zum Speichern in der Datenbank kommt auf dem Server die im Kapitel \ref{proj:sdkdbprocedcaller} n\"aher erl\"auterte Helferklasse zum Aufruf von gespeicherten Datenbankprozeduren zum Einsatz. In Zend werden die sogenannten "`Helper Broker"' benutzt, um die Helfer zu empfangen. Um die Helferklassen benutzen zu k\"onnen, m\"ussen sie erst in der \textit{Bootstrap}-Klasse des Modules eingetragen werden. Das geschieht folgenderma\ss{}en: {\small \texttt{Zend\_Controller\_Action\_HelperBroker::addPrefix("`SDK\_Helper\_"')}}.\\
Um die Art des Zugriffs auf die Helferklasse im Codebeispiel \ref{code:phpspeicherndb} zu erm\"oglichen, wird im Helfer Broker die von PHP bereitgestellte \textit{magische} Methode \texttt{\_\_get()} aufgerufen. In der Methode wird dann nach einer Klasse mit dem Namen "`DbProcedureCaller"' gesucht. Die Methode der Helfer Klasse ruft die Stored Procedure "`deleteTableRow"' und "`deleteTableRow"' [Kapitel \ref{proj:dbaufbau}] auf.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=86,lastline=93,
		captionpos=b,
		caption={Einsatz von DbProcedureCaller},
		label=code:phpspeicherndb]{media/phpcode.php}
		
Um auch greifbare Ergebnisse zu sehen, f\"uge ich die Abbildung \ref{fig:uitables} hinzu. Mein Userinterface gruppiert zu diesem Zweck den Inhalt der externen Quellen in Tabs. Hier erkennt man, dass es sich bei der ersten Quelle um eine MySQL-Datenbank handelt und bei der zweiten um eine CSV-Datei, die an einem entfernten FTP-Server liegt.

\begin{figure}[htbp]
	\centering
	\includegraphics[width=13cm]{media/uitabellenaussuchen.PNG}
	\caption{Auswahl der Datenmengen aus den externen Quellen}
	\label{fig:uitables}
\end{figure}

\clearpage

\subsubsection{Attributenauswahl pro Datenmenge}
Im zweiten Akt des Konfigurationsassistenten sucht der Administrator die Attribute aus den zuvor gew\"ahlten Datenkollektionen aus, das hei\ss{}t die vertikale Filterung der Daten wird hier bestimmt. Mein Design dieser Seite erkl\"art sich in der Abbildung \ref{fig:uicolumns}. Hier sieht man beispielsweise der Aufbau einer zuor selektierten Tabelle "`peron"' aus einer SqlQuelle dargestellt. Die Struktur der CSV-Datei wird \"ahnlich dargestellt. Die Tabelle enth\"alt wiederrum ein HTML-Formular aus Checkboxen. Die Implementierung dieses Teil der Webseite ist bis auf die spezifischen Details mit deorherigen Schritt in [ Unterkapitel \ref{proj:tabellenauswahl}] identisch. Zur Speicherung der Eingaben kommen die Datenbankprozedure [Kapitel \ref{proj:dbaufbau}] "`deleteColumn"' und "`saveTableColumn"' zum Einsatz.

\begin{figure}[htbp]
	\centering
	\includegraphics[width=11cm]{media/uicolumnsaussuchensql.PNG}
	\caption{vertikale Filterung}
	\label{fig:uicolumns}
\end{figure}

\clearpage

\subsubsection{Angaben zur Datenverschmlezung}
\label{proj:dataerschmelzung}
Im Letzten Schritt des Konfigurationsassistenten erfolgen Angaben dazu, wie die Datenmengen zusammengebracht werden sollen.

\begin{figure}[htbp]
	\centering
	\includegraphics[width=11cm]{media/uijoinuebersicht.PNG}
	\caption{\"Ubersicht der Verschmelzungsregeln}
	\label{fig:uijoinuebersicht}
\end{figure}

Zuerst erscheint eine \"Ubersichtsseite. Auf dieser Seite erh\"alt man die Optionen, beim Click auf dem Link "`L\"oschen"' Regeln zu entfernen und beim Click auf den Knopf "`hinzuf\"ugen"' neue Regeln zu definieren. Das L\"oschverfahren wird beim Aufruf der Datenbankprozedur "`deleteJoinColumn"' [sieh Kapitel \ref{proj:dbaufbau}] eingeleitet. Zur Programmierung ist es wichtig zu erw\"ahnen, dass die zu repr\"asentierenden Daten dieser Seite von der Datenbankprozedur [Kapitel \ref{proj:dbaufbau}] "` findJoinsByViewId(viewId)"' stammen. Die folgende Abbildung \ref{fig:uifindjoinsbyviewid} zeigt zur Veranschaulichung die Ergebnisse in einer Tabelle in der phpMyAdmin-Umgebung.

\begin{figure}[htbp]
	\centering
	\includegraphics[width=8cm]{media/uifindJoinsByViewId.PNG}
	\caption{\"Ubersicht der Verschmelzungsregeln}
	\label{fig:uifindjoinsbyviewid}
\end{figure}

Zum Einf\"ugen neuer Regeln wird man auf eine neue Seite weitergeleitet. Auf dieser Seite werden die Regeln in nummerierten Gruppen angezeigt. Der Administrator w\"ahlt aus einer Dropdownliste die gew\"unschten Datenmengen aus. Nach der Auswahl beider Partner wird die n\"achste Zeile des Formulars per Ajax geladen. Diese zeigt ihrerseits zwei Dropdownlisten mit den Attributen der k\"urzlich selektierten Tabellen. Ein Algorithmus untersucht die Eigenschaften der Attribute und macht einen Vorschlag zum Aussehen der Regel. Das View-Script zeigt den Vorschlag an, indem es die Elmente der Liste vorselektiert. Beispielhaft zeigt die Abbldung \ref{fig:uijoin} die Vorselektion der Spalten "`person\_id"' bei der Tabelle "`bestellungen"' und der Spalte "`id"' bei der Tabelle "`person"'. Dazu geh\"ort ebenso eine Vergleichsoperation, die in der Abbildung \ref{fig:uijoin} mit "`="' zu erkennen ist. Andere Vergleichsoperationen sind in der lokalen Datenbank in der Tabelle "`JoinColumns"' als ENUM-Werte gespeichert [Kapite \ref{proj:analysdesign}].

\begin{figure}[htbp]
	\centering
	\includegraphics[width=11cm]{media/uijoin.PNG}
	\caption{Regeldefinition zur Datenverschmelzung}
	\label{fig:uijoin}
\end{figure}

Es soll nun kurz auf den partiellen View-Helfer von Zend eingegangen werden, die bei der Programmierung der Webseite zum Einsatz kommen. Er wird \textit{Partial} gennant und dient zum Rendern oder zur Wiederverwendung von TemplatesfragmenteN innerhalb seines eigenen oder eines anderen Variablenbereichs. Es existiert in Zend zus\"atzlich der PartialLoop, um das gleiche Inhaltsfragment in einer Schleife mehrmals darzustellen. Dazu erstelle ich im Viewordner einen neuen Ordner \texttt{/views/partial}. Im Partialordner stehen nun die Templatesfragmente zur Darstellung der per Ajax zu ladenden Teilformulare. Der erste Parameter gibt an, wo das phtml-Skript zu finden ist. Der zweite ist optional und zeigt an, ob es zu einer Modulview geh\"ort. Mit dem dritten Parameter \"ubergibt man die Viewdaten.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=151,lastline=154,
		captionpos=b,
		caption={Partial View Helper},
		label=code:phppartial]{media/phpcode.php}

%
%---------------------------------------------------------------------
%
\section{Anbindung der Datenquellen}
\label{sec:abstrakteanbindungderdatenquellen}	
\label{proj:adapter}
Wie schon in den Anforderungen genannt wurde, k\"onnen die Datenquellen uneinheitlich sein. Daher ist das Schaffen einer Abstraktionsebene mit einer einheitlichen Schnittstelle als einen gemeinsamen Nenner, einerseits zur Interaktion mit den ausw\"artigen Quellen und andererseits zum Zusammenwirken mit dem Rest des Modules, ein sehr wichtiger Punkt. Dazu arbeite ich bei der Konzeption dieses Teils des Moduls mit den \textit{Adapterpattern} [Kapitel \ref{subsec:adapterpattern}].\\
Das folgende Klassendiagramm \ref{fig:adapterklassendiagramm} ist eine Darstellung des Aufbaus der Adapterklassen und deren Abh\"angigkeiten untereinander. Die Adapter sind in Typen unterteilt. Jeder Typ dient als Schnittstelle nach au\ss{}en, zur Kommunikation mit einer bestimmten Quellenart. Auf diese Weise lassen sich die Adapter nach Typen klassifizieren und besser modellieren. Das Diagramm erh\"alt jedoch nur Angaben zu den wichtigsten Methoden und Datenelementen der einzelnen Klassen. Die Umsetzung ergibt mehr Eigenschaften und Funktionalit\"aten, die zu realisieren sind. Eine \"Ubersicht der Ordnerstruktur der Adapter findet man in der Abbildung \ref{fig:sdklib}.

\begin{figure}[htbp]
	\centering
	\includegraphics[width=12cm]{media/klassendiagrammadapter.PNG}
	\caption{Adapter-Klassendiagramm}
	\label{fig:adapterklassendiagramm}
\end{figure}

\newpage

	\subsection{Abstrakte Adapter}
	\label{subsubsec:abstrakteadapter}
	\label{proj:abstrakteadapter}
	In meiner Konzeption zur Anbindung der externen Datenquellen existiert eine abstrakte Klasse \textbf{"`SDK\_Adapter\_Abstract"'}, die neben der statischen Methode \texttt{isSQL(\$adapterObj)}, allen Subklassen vorschreibt, dass ein Adapter in seiner fertigen Form noch mindestens drei Methoden zu implementieren hat. Diese Klasse \"ubernimmt so die Rolle einer  \textit{\texttt{interface}}-Klasse und bietet dar\"uberhinaus bereits fertig programmierte Funktionen.
	
	\begin{itemize}
	\item \texttt{public abstract function getType()}\\
		liefert liefert eine Auskunft dar\"uber, ob hinter dem mitgegebenen Adapterobjekt eine SQL-Datenbank steht. Dies ist zu einem sp\"ateren Zeitpunkt bei der Entscheidung hilfreich, ob die Quelle Join-Operationen unterst\"utzt, um diese dort auszuf\"uhren. \texttt{isSQL(\$adapterObj)} nutzt diese Funktion, um den Typen zu bestimmen.

		\item \texttt{public abstract function listTables()}\\
		Diese Methode listet alle Datens\"atze auf, die aus einer Quelle zu entnehmen sind. Im Falle einer relationalen Datenbank liefert die Methode eine Liste aller Tabellen, die in der Datenbank vorhanden sind. Bei einem Dateiadapter ("`CSV"', "`Excel"') werden die Worksheets aufgelistet.

		\item \texttt{public abstract function describeTable(\$tableName, \$schemaName)}\\
		F\"ur die Analyse der Daten ist das Wissen um ihren Aufbau essentiell. Hierbei ist diese Methode behilflich. Sie bietet eine einheitliche Schnittstelle zum Rest des Systems.
	\end{itemize}

	Die zweite abstrakte Klasse f\"ur die Fileadapter ist "`SDK\_Adapter\_File\_Abstract"'. Sie baut auf die "`SDK\_Adapter\_Abstract"' auf und bietet zus\"tzliche \textit{Getter} und \textit{Setter} Funktionen zum Dateiname und Dateipfad.\\
	Inspiriert von Zend und zur Minimierung der Entwicklungsaufwandes wird die Klasse "`SDK\_Model\_Table\_Metadata"' [Anhang \ref{anhang:sdkmodelmetadata}] als ein Teil der SDK. Diese wird in \texttt{describeTable} benutzt, um bei der Beschreibung der Datenstruktur eine homogene Form mit vorbestimmten Schl\"usselw\"ortern zu gew\"ahrleisten. Das ist besonders n\"utzlich bei der Analyse der Daten, um beispielsweise bei der Benutzeroberfl\"ache einen Vorschlag Verschmelzungsregeln zu machen. [Unterkapitel \ref{proj:dataerschmelzung}].  Bei der Beschreibung werden zu jeder Spalte einer Tabelle folgende Kriterien erl\"autert:\\
	Quellenname oder Datenbank (SCHEMA\_NAME), Wie die Tabellenbezeichnung (TABLE\_NAME), der  Name des Attributes (COLUMN\_NAME), seine Position (COLUMN\_POSITION), sein Datentyp (DATA\_TYPE), obligatorische Existenz (NULLABLE), Prim\"arschl\"ussel(PRIMARY), die Position bei zusammengesetzten Schl\"ussel (PRIMARY\_POSITION), Eindeutigkeit(IDENTITY).\\
	Im folgenden Beispiel wird die Beschreibung der Tabelle "`person"' aus einer SQL-Datenbank dargestellt.
	\\
	\lstinputlisting[
		breaklines=true,
		firstline=55,lastline=92,
		captionpos=b,
		caption={Beschreibung der Datens\"atze},
		label=code:describetables]{media/layout.phtml}
	

	\subsection{Konkrete Adapter}
	\label{subsubsec:konkreteadapter}
	\label{proj:konkreteadapter}
	Wie in den Anforderungen vereinbart, begrenze ich mich bei der Umsetzung des Projekts auf zwei Arten externer Quellen: SQL und CSV-Datei, die \"uber einen FTP-Server zu erreichen ist. Bei der Entwicklung nutze ich die Flexibilit\"at des Zend Frameworks und seiner Adapterklassen zur Anbindung von Datenbanken. So enthält die Klasse ein Datenbankobjekt vom Typ "", das im Konstruktor instanziiert wird, und benutzt es bei der Implementierung der durch die abstrakte Klasse "" vorgeschriebenen Methoden.

		\subsubsection{Datenbankadapter (SQL)}
		Bei dem SQL-Adapter hadelt es sich um die Klasse "`SDK\_Adapter\_Database\_MySQL"'. Bei der Entwicklung nutze ich die Flexibilit\"at des Zend Frameworks und seiner Adapterklassen zur Anbindung von Datenbanken. So enth\"alt die Klasse ein Datenbankobjekt vom Typ "`Zend\_Db\_Adapter\_Pdo\_Mysql"', das im Konstruktor instanziiert wird, und benutzt es bei der Implementierung der durch die abstrakte Klasse "`SDK\_Adapter\_Abstract"' vorgeschriebenen Methoden.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=156,lastline=168,
		captionpos=b,
		caption={Implementierung des SQL-Adapters},
		label=code:sdkmysqladapter]{media/phpcode.php}
		
		\newpage
		
		\subsubsection{Fileadapter (CSV)}
		Um den Fileadapter zu realisieren, wird eine externe Bibliothek Namens \textit{PHPExcel} \footnote{PHPExcel - OpenXML - Read, Write and Create Excel documents in PHP - Spreadsheet engine \url{http://phpexcel.codeplex.com/}.} eingesetzt. Sie ist mit dem Zend Framework kompatibel und bekannt f\"ur ihren Funktionsumfang. Die Installation erfolgt durch das Entpacken des heruntergeladenen Archivs im \textit{library}-Ordner. Anschlie\ss{}end wird der Namensraum "`PHPExcel\_"' beim ZendAutoloader im Controller [sieh Kapitel \ref{proj:sdk} zur Anbindung der SDK] registriert.\\
		Auf die eigentliche Funktionsweise des Fileadapters soll nun kurz eingegangen werden. Die Klasse "`SDK\_Adapter\_File\_Abstract"' verwaltet ein FTP-Adapterobjekt. Der FTP-Adapter l\"adt die Datei von einem entfernten Server herunter und speichert sie lokal auf dem Filesystem. Dies geschieht allerdings nur, wenn wenn die lokale Datei entweder nicht vorhanden oder nicht mehr aktuell ist. Dazu existiert die Methode \texttt{getLastModifiedTime(\$remote\_file)}, die intern die PHP-Funkiton \texttt{ftp\_mdtm} ausf\"uhrt. Diese Funktion liefert einen Zeitstemple, der den Zeitpunkt der letzten Dateieditierung auf dem Remoteserver anzeigt. Der Zeitstempel des Servers soll gr\"o\ss{}er oder gleich dem Zeitstempel der lokalen Datei sein, welcher mit \texttt{filemtime} ermittelt werden kann. Der Download der Datei kann mit dem Setzen der booleschen Variable \texttt{\$force\_download} in der Methode \texttt{getFile(\$remote\_file, \$force\_download = false)} erzwungen werden. Der Zusammenhang entsteht in der Methode \texttt{getFileName} der Klasse "`SDK\_Adapter\_File\_Abstract"', die intern \texttt{getFile} ausf\"uhrt.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=170,lastline=213,
		captionpos=b,
		caption={Implementierung des FTP-Adapters},
		label=code:sdkftpadapter]{media/phpcode.php}	

		Die Klasse "`SDK\_Adapter\_File\_CSV"' ist eine Subklasse der abstrakten Klasse "`SDK\_Adapter\_File\_Abstract"', damit erbt sie das FTP-Adapterobjekt von der Vaterklasse. Ihre Eigenschaften setzen sich aus einer Delimetervariable (deutsch Trennzeichen), welche die Art des Zeichens zur Abgrenzung von Daten in der CSV-Datei angibt, und einem PHPExcel-Objekt zusammen. In der Methode \texttt{parseCSV(\$force\_parse = false)} wird die Datei mit Hilfe der Bibleothek "`PHPExcel"' zu einem verschachtelten Array geparst und die Ergebnisse werden der Variable \texttt{protected \$\_parsedFileContent} zugewiesen. Hier wird zur Laufzeit der Vorgang zum Parsen nicht bei jedem Aufruf in Gang gesetzt, dies kann jedoch auf Wunsch erzwungen werden.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=216,lastline=247,
		captionpos=b,
		caption={Implementierung des CSV-Adapters},
		label=code:sdkcsvadapter]{media/phpcode.php}	
		
Das Ergebnis soll anhand des folgenden Beispiels demonstriert werden.
	\\
	\lstinputlisting[
		breaklines=true,
		firstline=94,lastline=121,
		captionpos=b,
		caption={Inhalt einer SCV-Datei},
		label=code:csparsed]{media/layout.phtml}
	
	\subsection{Instanziieren der Adapertobjekte}
	\label{proj:instanzadapter}
Zur Laufzeit ist der Zeitpunkt des ben\"otigten Adaptereinsatzes, jedoch nicht die Art des Adapters bekannt. Um die Instanziierung dynamischer zu gestallten, greife ich auf die \textit{Factory Methode} Pattern [Kapitel Design Pattern \ref{subsec:factorymethode}] zur\"uck.
Die Klasse "`SDK\_Adapter"' beinhaltet die Logik zur Unterscheidung, von welcher Klasse ein Objekt erzeugt werden soll.
Die Methode "`public static factory(\$config, ...)"' ist eine \"offentlich-statische und somit einfach aufgerufen werden. Sie analysiert die Konfigurationsangaben und ordnet sie einer bestimmten Adapterklasse zu. Anschlie\ss{}end wird ein Objekt erstellt und zur\"uckgegeben.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=249,lastline=276,
		captionpos=b,
		caption={SDK\_Adapter::factory},
		label=code:sdkfactoryadapter]{media/phpcode.php}	

%
%---------------------------------------------------------------------
%
\section{Datenverschmelzung}
\label{proj:join}
Obwohl die Fertigstellung der Entwicklung in der vorgegebenen Zeit nicht gelungen ist, m\"ochte ich an dieser Stelle einige \"Uberlegungen zur m\"oglichen praktischen Umsetzung der Datenverschmelzung festhalten.\\
Die aus den Adaptern gewonnene Datens\"atze sind in einem Array organisiert. Die Abbildung \ref{code:dataarray}. zeigt ein Beispiel von zwei Datens\"atzen. Im ersten Array sind Personendaten enthalten, im zweiten Bestellungen der jeweiligen Personen gespeichert. Nun sollen die Bestellungsdaten um die Daten der Personen erweitert werden. Zur Verdeutlichung des Sachverhaltes werden die Bestellungen mit "`Links"' und die Personen mit "`Rechts"' bezeichnet.
\\
	\lstinputlisting[
		breaklines=true,
		commentstyle=\color{CommentColor},
		firstline=124,lastline=162,
		captionpos=b,
		caption={Beispiel eines Datenarray},
		label=code:dataarray]{media/layout.phtml}

Der Algorithmus zur Zusammenf\"uhrung der Daten gruppiert den rechten Datensatz (Personen) nach der ersten Spalte, n\"amlich dem Prim\"arschl\"ussel (ID-Nummer), der bei der Konfiguration vom Administrator gew\"ahlt wirde [sieh Abbildung \ref{fig:uifindjoinsbyviewid}]. In einer for-Schleife \"uber den rechten Datenarray (Bestellungen) wird jede Zeile der Bestellungsdaten um einen Eintrag mit dem dazugeh\"orige Personendaten erweitert. 
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=308,lastline=320,
		captionpos=b,
		caption={Pseudocode: Teil des Algorithmus zur Datenzusammenf\"uhrung},
		label=code:algozusammen]{media/phpcode.php}
		
F\"ur die Verarbeitung von mehr als zwei Datens\"atzen, werden die Datens\"atze mit Hilfe einer Queue organisiert. So kann eine rekursive Ausf\"uhrung auf die Ergebnisse der ersten beiden Elemente mit dem n\"achststehenden Element erfolgen, bis die Warteschlange leer ist.



%
%---------------------------------------------------------------------
%
\section{Caching}
\label{proj:caching}
Cache "`bezeichnet in der EDV einen schnellen Puffer-Speicher, der (erneute) Zugriffe auf ein langsames Hintergrundmedium oder aufw\"andige Neuberechnungen zu vermeiden hilft"'\cite{bib:wikicache}\\
\\
Im Rahmen dieser These lasse ich die Schnittstellenklasse nach der Vorbereitung der Daten diese in einem Cache verwalten. Der Cache besitzt typischerweise eine G\"ultigkeitsdauer. Beim Eingang einer Clientanfrage wird erst gepr\"uft, ob der Cacheinhalt noch g\"ultig ist. Wenn der Fall eintrifft, dann werden die Daten aus dem Cacheinhalt gelesen und weitergegeben. Anderenfalls m\"ussen die Daten generiert [Kapitel \ref{proj:join}], gecacht und anschlie\ss{}end gesendet werden [sieh Abbildung \ref{fig:prozessclientabfragen} und Kapitel \ref{proj:analysdesign}].\\
\\
Nach einer intensiven Recherche zum Thema Caching in Bezug auf PHP und Zend ergeben sich viele M\"oglichkeiten zur Gestaltung des Cachemechanismus. Die erste Alternative ist beim Zend Framework zu bleiben. Die Nachteile beim "`Zend\_Cache"'\footnote{Zend\_Cache \url{http://framework.zend.com/manual/1.12/de/zend.cache.html}} entsteht durch typische Problematiken des Frameworks. Es ist an sehr spezielle Anwendungsf\"alle angepasst und bietet einen m\"achtigen Funktionalit\"atsumfang, was jedoch eine detaillierte und zeitintensive Einarbeitung ben\"otigt.\\
\\
Als Ausweichvariante l\"asst sich "`phpfastCache"'\footnote{phpFastCache: "`is a high-performance, distributed object caching system, generic in nature, but intended for use in speeding up dynamic web applications by alleviating database load."' \url {http://www.phpfastcache.com/}.} finden. Sie Unterst\"utzt mehrere Cachetreiber auch APC [Kapitel \ref{proj:primcache}]. Die Klasse zeichnet sich durch hohe Performanz und simple Nutzung aus. phpFastCache aus einer Klasse in einer einzelnen Datei und bietet den Entwicklern einheitliche API's. Auf diese Weise kann k\"unftig zwischen den von der Klasse unterst\"utzten Cachetreibern ohne die Notwendigkeit den Code zu modifizieren gewechselt werden. Das Cachen mit phpFastCache funktioniert wie ein Key-Value-Speicher.
	
	\subsection{Primitives Cachen(Key-Value)}
	\label{proj:primcache}
	F\"ur PHP existieren diverse Cache-Erweiterungen. Ich bevorzuge aufgrund seiner Verbreitung und Einfachheit bei der Nutzung sowie Installation das Zusatzmodul "`Alternative PHP Cache (APC)"'\footnote{APC: \url{http://www.php.net/manual/de/book.apc.php} und Download \url{http://pecl.php.net/package/APC}.}. Durch das Zwischenspeichern von aufwendig interpretierten PHP-Skripten, kann eine Beschleunigung bei der Ausf\"uhrung erreicht werden. Zus\"atzlich kann das APC-Modul benutzt werden, um einen Key-Value-Cachemechanisumus zu produzieren. Vorausgesetzt der Installation des PECL-Pakets erfolgt die Installation der APC-Treiber mit dem Konsolenbefehl \texttt{pecl install apc}.\\
	\\
	Die von mir entwickelte Cacheklasse baut auf den \textit{Singelton Pattern} auf und nutzt dabei den "`phpFastCache"'. Damit soll erreicht werden, dass zu einem Zeitpunkt stets genau eine Instanz zur Verwaltung der Cachespeicher eingesetzt wird. Das Singelton-Prinzip wird erreicht, indem der Konstruktor der Klasse auf "`private"' gesetzt und somit die M\"oglichkeit der Instanziierung der Klasse von au\ss{}en verboten wird. Die einzelne Instanz ist ein Attribut der Klasse selbst, das nicht nach au\ss{}en sichtbar ist. Diese wird dann durch eine \"offentlich-statische Methode, typischerweise \textit{getInstance()}, benannt.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=278,lastline=296,
		captionpos=b,
		caption={Klasse SDK\_Caching},
		label=code:sdkcaching]{media/phpcode.php}	
	
	Mit "`phpFastCache"' k\"onnen Objekte ebenfalls zwischengespeichert werden. Da sie erst serialisiert werden, empfiehlt sich die Implementierung des Interfaces "`Serializable"'. Die Notwendigkeit dazu entsteht durch die fehlende Speicherung bestimmter Datenelemente eines Objekts, die mit "`private"' oder "`protected"' gesch\"utzt sind und bei der Deserialisierung somit verloren gehen.\\
Folgender Codeblock soll die simpele Nutzung der Klasse "`SDK\_Cache"' demonstrieren.
\\
\lstinputlisting[
		language=PHP,
		breaklines=true,
		keywordstyle=\color{KeywordBlueColor},
		commentstyle=\color{CommentColor},
		stringstyle=\color{GrayColor},
		morekeywords={function,return,class,extends,public,private,protected},
		firstline=298,lastline=306,
		captionpos=b,
		caption={Einsatz von SDK\_Caching},
		label=code:sdkcachingeinsatz]{media/phpcode.php}
